﻿

using System;
using System.Collections.Generic;
using System.Windows;

namespace DataLoadingModule.ViewModel.LoadDataSet
{
    class DataTypeValidator
    {

        //dataset will typically be
        //{obj-id, traj-id, date(dd/mm/yyyy), time(hh:mm:ss), lat, lon, x, y}

        private readonly Dictionary<int, string> _lockedInDatatypeDictionary;
        private readonly string[] _actualDataValues;

        public DataTypeValidator(Dictionary<int, string> lockedInValues, string[] delimitedDatasetValues)
        {
            _lockedInDatatypeDictionary = lockedInValues;
            _actualDataValues = delimitedDatasetValues;
        }

        public bool ValidateData()
        {
            for (int i = 0; i < _lockedInDatatypeDictionary.Count; i++)
            {
                if(ValidateByDataType(i) == false)
                {
                    return false;
                }
            }
            return true;
        }

        private bool ValidateByDataType(int lockedInIndex)
        {
            bool isValidDataType = false;
            var analysedDataType = _lockedInDatatypeDictionary[lockedInIndex].ToLower();
            var analysedDataValue = _actualDataValues[lockedInIndex];

            if(analysedDataType.Contains("object") || analysedDataType.Contains("trajectory")) 
            {
                //for Object-Id & //for Trajectory-Id
                isValidDataType = IsValidGeneralString(analysedDataValue, analysedDataType);
            }

            else if (analysedDataType.Contains("lati") || analysedDataType.Contains("longi") || analysedDataType.Contains("coord")) 
            {
                //for latitude, longitude, x coord, y coord
                isValidDataType = IsValidAllNumbers(analysedDataValue, analysedDataType);
            }

            else if (analysedDataType.Contains("time") || analysedDataType.Contains("date"))
            {
                //for time and date
                isValidDataType = IsValidDateTime(analysedDataValue, analysedDataType);
            }

            return isValidDataType;

        }

        //validity tests

        private string MakeInValidTypeMessage(string valueToValidate, string supposedDataType, string specificMessage)
        {
            string generalMessage = "The datatype, '" + supposedDataType + "' had a value: '" + valueToValidate + "'.";
            return generalMessage + specificMessage;
        }

        private bool IsValidGeneralString(string valueToValidate, string supposedDataType)
        {

            //checks that string is not null, whitespace, or empty
            if (string.IsNullOrEmpty(valueToValidate) || string.IsNullOrWhiteSpace(valueToValidate))
            {
                ShowInvalidTypeMessageBox(MakeInValidTypeMessage(valueToValidate, supposedDataType, 
                    "This is invalid because the value was null or empty please change this." + "\n"));
                return false;
            }

            return true;
        }

        private bool IsValidAllNumbers(string valueToValidate, string supposedDataType)
        {
            double valueToConvert;
            var isValidNumber = Double.TryParse(valueToValidate, out valueToConvert);
            if(isValidNumber == false)
            {
                ShowInvalidTypeMessageBox(MakeInValidTypeMessage(valueToValidate, supposedDataType,
                    "This is invalid because the value must be a number." + "\n"));
            }
            return isValidNumber;
        }

        private bool IsValidDateTime(string valueToValidate, string supposedDataType)
        {
            DateTime valueToConvert;
            var isValidDateTime = DateTime.TryParse(valueToValidate, out valueToConvert);
            if (isValidDateTime == false)
            {
                ShowInvalidTypeMessageBox(MakeInValidTypeMessage(valueToValidate, supposedDataType,
                    "This is invalid because the value entered was not a valid date/time." + "\n"));
            }
            return isValidDateTime;
        }

        //show message box

        private void ShowInvalidTypeMessageBox(string message)
        {
            MessageBox.Show(message);
        }
    }
}
